﻿using System;
using System.Collections.Generic;
using System.IO;

namespace Aeon.Emulator.Interrupts
{
    /// <summary>
    /// Provides default handling of interrupts which signal error conditions (00h, 04h, 06h).
    /// </summary>
    internal sealed class ErrorHandler : IInterruptHandler
    {
        /// <summary>
        /// Initializes a new instance of the ErrorHandler class.
        /// </summary>
        public ErrorHandler()
        {
        }

        /// <summary>
        /// Gets the interrupts which are handled by this handler.
        /// </summary>
        IEnumerable<InterruptHandlerInfo> IInterruptHandler.HandledInterrupts
        {
            get { return new InterruptHandlerInfo[] { 0x00, 0x04, 0x06 }; }
        }
        /// <summary>
        /// Called when the interrupt handler should perform its action.
        /// </summary>
        /// <param name="interrupt">Raised interrupt number.</param>
        void IInterruptHandler.HandleInterrupt(int interrupt)
        {
            switch(interrupt)
            {
            case 0x00:
                throw new InvalidOperationException("Unhandled divide-by-zero.");

            case 0x04:
                throw new InvalidOperationException("Unhandled numeric overflow.");

            case 0x06:
                throw new InvalidOperationException("Unhandled undefined opcode.");
            }
        }
        /// <summary>
        /// Invoked when the emulator enters a paused state.
        /// </summary>
        void IVirtualDevice.Pause()
        {
        }
        /// <summary>
        /// Invoked when the emulator resumes from a paused state.
        /// </summary>
        void IVirtualDevice.Resume()
        {
        }
        /// <summary>
        /// Invoked when the virtual device has been added to a VirtualMachine.
        /// </summary>
        /// <param name="vm">VirtualMachine which owns the device.</param>
        void IVirtualDevice.DeviceRegistered(VirtualMachine vm)
        {
        }
        /// <summary>
        /// Invoked when the device should save its current state to a <see cref="System.IO.Stream"/>.
        /// </summary>
        /// <param name="destination"><see cref="System.IO.Stream"/> to which the state is saved.</param>
        void IVirtualDevice.SaveCurrentState(Stream destination)
        {
        }
        /// <summary>
        /// Invoked when the device should restore its state from a <see cref="System.IO.Stream"/>.
        /// </summary>
        /// <param name="source"><see cref="System.IO.Stream"/> from which the state is restored.</param>
        void IVirtualDevice.RestoreState(Stream source)
        {
        }
        /// <summary>
        /// Performs application-defined tasks associated with freeing, releasing, or resetting unmanaged resources.
        /// </summary>
        void IDisposable.Dispose()
        {
        }
    }
}
